feat: add support for custom rules. Move rules and gitleaks logic to 2ms#367
Merged
cx-diogo-rocha merged 16 commits intomasterfrom Jan 19, 2026
Merged
feat: add support for custom rules. Move rules and gitleaks logic to 2ms#367cx-diogo-rocha merged 16 commits intomasterfrom
cx-diogo-rocha merged 16 commits intomasterfrom
Conversation
<!-- Thanks for contributing to 2ms by offering a pull request. --> Closes # **Proposed Changes** - Fully moved rules from gitleaks to our own, to package ruledefine - Validations that previously occurred, for every rule, every time 2ms ran, now run in unit tests - Created new rule struct, replacing our previous rule struct that wrapped gitleaks Rule. - The new Rule struct has all fields that are in practice used by gitleaks Rules; fields which are not used by default rules of gitleaks were not included. - **Breaking change:** - ruleID became a uuid4 that identifies a rule regardless of its name. The old ruleID became ruleName - ignores and selects with flags --ignore-rule and -rule still work with old ruleIDs. - **Breaking change** - ids of results have changed, now take into account the new uuid4 ruleID. - ignores with on -config file or in --ignore-result will not longer properly ignore those results because the id of results changed - Added new fields to results: - severity - for now High as default for every rule. Rules that can perform validation on their results (eg, github-pat) will bump the severity to Critical if the secret is Valid; and lower the severity to Medium if the secret is Invalid - ruleCategory - used to classify and groups rules - ruleName - the exact same as old ruleID The purpose of these changes is to allow us to have more control over the rules, in preparation for: 1. Allowing users to create their own rules in the open source tool. In the future the user will be able to define more fields than simply the regex (currently supported with --regex flag) 2. Allowing query editing in Checkmarx One. **Changes to rules** - clojars-api-token - reintroduced entropy to 2, like it is in gitleaks - github-app-token - reintroduced entropy to 3, like it is in gitleaks - plaid-client-id - updated entropy from 3 to 3.5, like it is in gitleaks - vault-service-token - updated regex according to latest version of gitleaks; reintroduced entropy to 3.5, like it is in gitleaks **Checklist** - [x] I covered my changes with tests. - [x] I Updated the documentation that is affected by my changes: - [x] Change in the CLI arguments - [x] Change in the configuration file I submit this contribution under the Apache-2.0 license.
<!-- Thanks for contributing to 2ms by offering a pull request. --> Closes # **Proposed Changes** - Introduced flag --custom-rules-path which supports passing a file of type JSON or YAML. This file has to be a list of ruledefine.Rule, and can be used to define custom rules to be used in the scan Custom Rules can be: - Overrides - if a rule present in the file shares the same ruleId as a default rule of 2ms, the rule present in the file will replace (override) the default rule in the scan. If a rule is overridden, it will simply take all fields from the rule as defined in the file. You must include all fields that you want to be defined, otherwise they will be nil/empty. - New rules - if a rule does not share ruleId with a default rule, it will be appended to the list of rules used in the scan. - Rules can now be ignored by ruleId - Custom rules work properly with --rule and --ignore-rule flags. Rules can be selected/ignored by ruleId, ruleName and tag. **Note:** Rules defined in the custom rules can find duplicate results with each other or with default rules. 2ms doesn't match or correlate results found by different rules, it will be the responsibility of the user to avoid situations like these. **One exception** is generic-api-key and overrides of generic-api-key, whose results will be ignored if found by any other rule in the scan. This behavior already happened in the default generic-api-key and was extended to overrides of this rule. **Checklist** - [x] I covered my changes with tests. - [x] I Updated the documentation that is affected by my changes: - [x] Change in the CLI arguments - [ ] Change in the configuration file I submit this contribution under the Apache-2.0 license.
<!-- Thanks for contributing to 2ms by offering a pull request. --> Closes # **Proposed Changes** <!-- Please describe the big picture of your changes here. If it fixes a bug or resolves a feature request, be sure to link to that issue. --> **Checklist** - [x] I covered my changes with tests. - [ ] I Updated the documentation that is affected by my changes: - [ ] Change in the CLI arguments - [ ] Change in the configuration file I submit this contribution under the Apache-2.0 license.
…#351) <!-- Thanks for contributing to 2ms by offering a pull request. --> Closes # **Proposed Changes** <!-- Please describe the big picture of your changes here. If it fixes a bug or resolves a feature request, be sure to link to that issue. --> **Checklist** - [ ] I covered my changes with tests. - [ ] I Updated the documentation that is affected by my changes: - [ ] Change in the CLI arguments - [ ] Change in the configuration file I submit this contribution under the Apache-2.0 license.
…295-custom-rules # Conflicts: # README.md # go.mod # lib/reporting/report_test.go # lib/reporting/sarif.go
…of Rule (#356) <!-- Thanks for contributing to 2ms by offering a pull request. --> Closes # **Proposed Changes** <!-- Please describe the big picture of your changes here. If it fixes a bug or resolves a feature request, be sure to link to that issue. --> **Checklist** - [ ] I covered my changes with tests. - [ ] I Updated the documentation that is affected by my changes: - [ ] Change in the CLI arguments - [ ] Change in the configuration file I submit this contribution under the Apache-2.0 license.
…ion bug (#363) **New Limit Flags** --max-findings: Caps the total number of findings across the entire scan. When the limit is reached, the scan stops early and reports results up to that limit. Set to 0 (default) to disable. --max-rule-matches-per-fragment: Limits the number of regex matches per rule per fragment (e.g., file, chunked file, page). Useful for preventing excessive matches in large files. Set to 0 (default) to disable. --max-secret-size: Ignores secrets larger than the specified size in bytes. Helps filter out false positives from large binary blobs or encoded content. Set to 0 (default) to disable. **Bug Fix** Fixed last-line detection: Secrets on the last line of files without a trailing newline are now correctly detected. The fix adds a virtual newline marker in the location calculation logic, removing the previous CxFileEndMarker workaround.
<!-- Thanks for contributing to 2ms by offering a pull request. --> Closes # **Proposed Changes** Updated version to v5. Updated README with a better explanation of entropy Changed jwt rule name to Jwt, now consistent with all other rules Added test for rule naming convention <!-- Please describe the big picture of your changes here. If it fixes a bug or resolves a feature request, be sure to link to that issue. --> **Checklist** - [ ] I covered my changes with tests. - [ ] I Updated the documentation that is affected by my changes: - [ ] Change in the CLI arguments - [ ] Change in the configuration file I submit this contribution under the Apache-2.0 license.
|
Great job! No new security vulnerabilities introduced in this pull request |
cx-leonardo-fontes
approved these changes
Jan 19, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.








Closes #
Proposed Changes
ran, now run in unit tests
wrapped gitleaks Rule.
gitleaks Rules; fields which are not used by default rules of gitleaks
were not included.
regardless of its name. The old ruleID became ruleName, but with different casing (generic-api-key->Generic-Api-Key)
old ruleIDs. Comparison of ruleNames (old ruleIDs) is performed with all characters in lower case.
account the new uuid4 ruleID.
properly ignore those results because the id of results changed
perform validation on their results (eg, github-pat) will bump the
severity to Critical if the secret is Valid; and lower the severity to
Medium if the secret is Invalid
--max-findings: Caps the total number of findings across the entire
scan. When the limit is reached, the scan stops early and reports
results up to that limit. Set to 0 (default) to disable.
--max-rule-matches-per-fragment: Limits the number of regex matches per
rule per fragment (e.g., file, chunked file, page). Useful for
preventing excessive matches in large files. Set to 0 (default) to
disable.
--max-secret-size: Ignores secrets larger than the specified size in
bytes. Helps filter out false positives from large binary blobs or
encoded content. Set to 0 (default) to disable.
Changes to rules
gitleaks
gitleaks; reintroduced entropy to 3.5, like it is in gitleaks
Checklist
I submit this contribution under the Apache-2.0 license.